home *** CD-ROM | disk | FTP | other *** search
/ QRZ! Ham Radio 8 / QRZ Ham Radio Callsign Database - Volume 8.iso / mac / files / infodata / callbook.tar / callbook_1.3 / canadian.c < prev    next >
C/C++ Source or Header  |  1991-04-03  |  8KB  |  475 lines

  1. /*
  2.  * The Canadian database from the DOC isn't in a very helpful format. They
  3.  * don't use standard abbreviations or anything like that and they bunch
  4.  * together different fields of information so it's virtually unparsable by
  5.  * machine. Anyway, this code tries to take this DOC file and put it in the
  6.  * FCC format. A heavy amount of AI (ie guessing) is done to try to get
  7.  * things into shape so I can't guarentee it will handle all situations or
  8.  * even do the right thing in all cases but it should be close. If it gets
  9.  * totally lost, it writes the bad line out so that it may be handled by
  10.  * hand. *PLEASE* SEND ME ANY IMPROVEMENTS TO THIS CODE.
  11.  */
  12.  
  13. #include <ctype.h>
  14. #include <stdio.h>
  15.  
  16. #define MAXLINE 1024
  17.  
  18. #define ORG_START 36
  19. #define ADDR_START 71
  20. #define CITY_START 106
  21. #define ZIP_START 141
  22. #define CALL_START 147
  23.  
  24. char buf[MAXLINE], first[MAXLINE], last[MAXLINE], addr[MAXLINE];
  25. char city[MAXLINE], prov[MAXLINE], zip[MAXLINE], call[MAXLINE];
  26.  
  27. char *backup(), *rindex();
  28.  
  29. main(argc, argv)
  30. int argc;
  31. char **argv;
  32. {
  33.     FILE *fd;
  34.  
  35.     fd = fopen(argv[1], "r");
  36.  
  37.     while (fgets(buf, MAXLINE, fd) != NULL) {
  38.  
  39.         /* pull the names out of the first field */
  40.  
  41.         if (!extract_names()) {
  42.             fprintf(stderr, "%s", buf);
  43.             continue;
  44.         }
  45.  
  46.         /* address is easy - just copy it over */
  47.  
  48.         strcpyblnks(addr, buf+ADDR_START, CITY_START-ADDR_START);
  49.  
  50.         /* separate the city and province as best you can */
  51.  
  52.         if (!extract_city()) {
  53.             fprintf(stderr, "%s", buf);
  54.             continue;
  55.         }
  56.  
  57.         /* just copy over the zip and the call */
  58.  
  59.         strcpyblnks(zip, buf+ZIP_START, CALL_START-ZIP_START);
  60.         strcpyblnks(call, buf+CALL_START, MAXLINE);
  61.  
  62.         printf("%s|%s||%s|||||%s|%s|%s|%s|||||||\n",
  63.                     call,last,first,addr,city,prov,zip);
  64.     }
  65.  
  66.     close(fd);
  67.  
  68.     exit(0);
  69. }
  70.  
  71.  
  72. /*
  73.  * Figure out the first and last name and load them into the buffers.
  74.  */
  75.  
  76. extract_names()
  77. {
  78.     int count, start, mark1=0, mark2=0, bound;
  79.  
  80.     bound = ORG_START;
  81.     count = 0;
  82.  
  83.     while (isspace(buf[count]))
  84.         count++;
  85.  
  86.     start = count;
  87.  
  88.     if (count >= ORG_START)
  89.         bound = ADDR_START;
  90.  
  91.     while (count < bound) {
  92.  
  93.         while (!isspace(buf[count]))
  94.             count++;
  95.  
  96.         mark2 = mark1;
  97.         mark1 = count;
  98.  
  99.         while (isspace(buf[count]))
  100.             count++;
  101.     }
  102.  
  103.     if (!mark1)
  104.         return 0;
  105.  
  106.     if (!mark2) {
  107.         *first = '\0';
  108.         strcpyblnks(last,buf+start,bound-start);
  109.     } else {
  110.         strcpyblnks(first,buf+start,mark2-start);
  111.         strcpyblnks(last,buf+mark2,bound-mark2);
  112.     }
  113.  
  114.     return 1;
  115. }
  116.  
  117.  
  118. /*
  119.  * Figure out the city and province name and load them into the buffers.
  120.  */
  121.  
  122. extract_city()
  123. {
  124.     int is_city = 0;
  125.     char *mark, *pnt, *oldpnt;
  126.  
  127.     pnt = backup(buf+ZIP_START);
  128.  
  129.     if (pnt == 0)
  130.         pnt = backup(rindex(buf+CITY_START, ','));
  131.  
  132.     if (pnt == 0) {
  133.         pnt = buf+CITY_START;
  134.         goto copy_city;
  135.     }
  136.  
  137.     switch (*pnt) {
  138.  
  139.         case 'a':    /* Alberta */
  140.         case 'A':
  141.             strcpy(prov, "AL");
  142.             break;
  143.  
  144.         case 'b':    /* New Brunswick or British Columbia */
  145.         case 'B':
  146.             if (*(pnt+1) == 'c' || *(pnt+1) == 'C') {
  147.                 strcpy(prov, "BC");
  148.                 break;
  149.             }
  150.  
  151.             if ((pnt = backup(oldpnt = pnt)) == 0) {
  152.                 strcpy(prov, "BC");
  153.                 pnt = oldpnt;
  154.             }
  155.  
  156.             if (*pnt == 'n' || *pnt == 'N') {
  157.                 strcpy(prov, "NB");
  158.                 break;
  159.             }
  160.  
  161.             strcpy(prov, "BC");
  162.             pnt = oldpnt;
  163.  
  164.             break;
  165.  
  166.         case 'c':    /* maybe British Columbia */
  167.         case 'C':
  168.             if ((pnt = backup(oldpnt = pnt)) == 0) {
  169.                 pnt = buf+CITY_START;
  170.                 goto copy_city;
  171.             }
  172.  
  173.             if (*pnt == 'b' || *pnt == 'B') {
  174.                 strcpy(prov, "BC");
  175.                 break;
  176.             }
  177.  
  178.             pnt = buf+CITY_START;
  179.             goto copy_city;
  180.  
  181.         case 'e':    /* maybe Prince Edward Island */
  182.         case 'E':
  183.             if ((pnt = backup(oldpnt = pnt)) == 0) {
  184.                 pnt = buf+CITY_START;
  185.                 goto copy_city;
  186.             }
  187.  
  188.             if (*pnt == 'p' || *pnt == 'P') {
  189.                 strcpy(prov, "PE");
  190.                 break;
  191.             }
  192.  
  193.             pnt = buf+CITY_START;
  194.             goto copy_city;
  195.  
  196.         case 'f':    /* maybe Newfoundland */
  197.         case 'F':
  198.             if ((pnt = backup(oldpnt = pnt)) == 0) {
  199.                 pnt = buf+CITY_START;
  200.                 goto copy_city;
  201.             }
  202.  
  203.             if (*pnt == 'n' || *pnt == 'N') {
  204.                 strcpy(prov, "NF");
  205.                 break;
  206.             }
  207.  
  208.             pnt = buf+CITY_START;
  209.             goto copy_city;
  210.  
  211.         case 'i':    /* maybe Prince Edward Island */
  212.         case 'I':
  213.             if ((pnt = backup(oldpnt = pnt)) == 0) {
  214.                 pnt = buf+CITY_START;
  215.                 goto copy_city;
  216.             }
  217.  
  218.             if (*pnt != 'e' && *pnt != 'E') {
  219.                 pnt = buf+CITY_START;
  220.                 goto copy_city;
  221.             }
  222.  
  223.             if ((pnt = backup(oldpnt = pnt)) == 0) {
  224.                 pnt = buf+CITY_START;
  225.                 goto copy_city;
  226.             }
  227.  
  228.             if (*pnt != 'p' && *pnt != 'P') {
  229.                 pnt = buf+CITY_START;
  230.                 goto copy_city;
  231.             }
  232.  
  233.             strcpy(prov, "PE");
  234.             break;
  235.  
  236.         case 'm':    /* Manitoba */
  237.         case 'M':
  238.             strcpy(prov, "MB");
  239.             break;
  240.  
  241.         case 'n':    /* New Bunswick, Nova Scotia, Newfoundland */
  242.         case 'N':    /* or the NorthWest Territory! */
  243.  
  244.             if (*(pnt+1) == 'b' || *(pnt+1) == 'B') {
  245.                 strcpy(prov, "NB");
  246.                 break;
  247.             }
  248.  
  249.             if (*(pnt+1) == 's' || *(pnt+1) == 'S') {
  250.                 strcpy(prov, "NS");
  251.                 break;
  252.             }
  253.  
  254.             if (*(pnt+1) == 'f' || *(pnt+1) == 'F') {
  255.                 strcpy(prov, "NF");
  256.                 break;
  257.             }
  258.  
  259.             if (*(pnt+1) == 'w' || *(pnt+1) == 'W') {
  260.                 strcpy(prov, "NW");
  261.                 break;
  262.             }
  263.  
  264.             if (*(pnt+1) == 'o' || *(pnt+1) == 'O') {
  265.  
  266.                 if (*(pnt+2) == 'v' || *(pnt+2) == 'V') {
  267.                     strcpy(prov, "NS");
  268.                     break;
  269.                 }
  270.  
  271.                 if (*(pnt+2) == 'r' || *(pnt+2) == 'R') {
  272.                     strcpy(prov, "NW");
  273.                     break;
  274.                 }
  275.  
  276.                 pnt = buf+CITY_START;
  277.                 goto copy_city;
  278.             }
  279.  
  280.             if (*(pnt+1) != 'e' && *(pnt+1) != 'E') {
  281.                 pnt = buf+CITY_START;
  282.                 goto copy_city;
  283.             }
  284.  
  285.             if (*(pnt+2) != 'w' && *(pnt+2) != 'W') {
  286.                 pnt = buf+CITY_START;
  287.                 goto copy_city;
  288.             }
  289.  
  290.             if (*(pnt+3) == 'b' || *(pnt+3) == 'B') {
  291.                 strcpy(prov, "NB");
  292.                 break;
  293.             }
  294.  
  295.             if (*(pnt+3) == 'f' || *(pnt+3) == 'F') {
  296.                 strcpy(prov, "NF");
  297.                 break;
  298.             }
  299.  
  300.             pnt = buf+CITY_START;
  301.             goto copy_city;
  302.  
  303.         case 'o':    /* Ontario */
  304.         case 'O':
  305.             strcpy(prov, "ON");
  306.             break;
  307.  
  308.         case 'p':    /* Prince Edward Island */
  309.         case 'P':
  310.             strcpy(prov, "PE");
  311.             break;
  312.  
  313.         case 'q':    /* Quebec */
  314.         case 'Q':
  315.             strcpy(prov, "PQ");
  316.             break;
  317.  
  318.         case 's':    /* Nova Scotia or Sasketchewan */
  319.         case 'S':
  320.             if ((pnt = backup(oldpnt = pnt)) == 0) {
  321.                 strcpy(prov, "SK");
  322.                 pnt = oldpnt;
  323.             }
  324.  
  325.             if (*pnt == 'n' || *pnt == 'N') {
  326.                 strcpy(prov, "NS");
  327.                 break;
  328.             }
  329.  
  330.             strcpy(prov, "SK");
  331.             pnt = oldpnt;
  332.  
  333.             break;
  334.  
  335.         case 't':    /* Yukon or Northwest Territories */
  336.         case 'T':
  337.             if ((pnt = backup(oldpnt = pnt)) == 0) {
  338.                 pnt = buf+CITY_START;
  339.                 goto copy_city;
  340.             }
  341.  
  342.             if (*pnt == 'y' || *pnt == 'Y') {
  343.                 strcpy(prov, "YT");
  344.                 break;
  345.             }
  346.  
  347.             if (*pnt == 'n' || *pnt == 'N') {
  348.                 strcpy(prov, "NW");
  349.                 break;
  350.             }
  351.  
  352.             if (*pnt != 'w' && *pnt != 'W') {
  353.                 pnt = buf+CITY_START;
  354.                 goto copy_city;
  355.             }
  356.  
  357.             if ((pnt = backup(oldpnt = pnt)) == 0) {
  358.                 pnt = buf+CITY_START;
  359.                 goto copy_city;
  360.             }
  361.  
  362.             if (*pnt == 'n' || *pnt == 'N') {
  363.                 strcpy(prov, "NW");
  364.                 break;
  365.             }
  366.  
  367.             pnt = buf+CITY_START;
  368.             goto copy_city;
  369.  
  370.         case 'w':    /* Northwest Territory */
  371.         case 'W':
  372.             if ((pnt = backup(oldpnt = pnt)) == 0) {
  373.                 pnt = buf+CITY_START;
  374.                 goto copy_city;
  375.             }
  376.  
  377.             if (*pnt != 'n' && *pnt != 'N') {
  378.                 pnt = buf+CITY_START;
  379.                 goto copy_city;
  380.             }
  381.  
  382.             strcpy(prov, "NW");
  383.             break;
  384.  
  385.         case 'y':    /* Yukon */
  386.         case 'Y':
  387.             strcpy(prov, "YT");
  388.             break;
  389.  
  390.         default:
  391.             pnt = buf+CITY_START;
  392.             goto copy_city;
  393.     }
  394.  
  395.     for (oldpnt = buf+CITY_START; oldpnt < pnt; oldpnt++)
  396.         is_city |= isalnum(*oldpnt);
  397.  
  398. copy_city:
  399.     if (is_city)
  400.         strcpyblnks(city, buf+CITY_START, pnt-buf-CITY_START);
  401.  
  402.     else {
  403.         *prov = '\0';
  404.         strcpyblnks(city, buf+CITY_START, ZIP_START-CITY_START);
  405.     }
  406.  
  407.     for (pnt=city+strlen(city)-1; *pnt==','; pnt--)
  408.         *pnt = '\0';
  409.  
  410.     if (strlen(city))
  411.         return 1;
  412.  
  413.     return 0;
  414. }
  415.  
  416. /*
  417.  * Back up to the begining of the previous word. Return zero if you hit comma.
  418.  */
  419.  
  420. char *
  421. backup(str)
  422. char *str;
  423. {
  424.     str--;
  425.  
  426.     while (*str != ',' && !isalnum(*str))
  427.         str--;
  428.  
  429.     if (*str == ',')
  430.         return 0;
  431.  
  432.     while (isalnum(*str))
  433.         str--;
  434.  
  435.     return str+1;
  436. }
  437.  
  438.  
  439. /*
  440.  * copy num bytes from src to dest. While you're at it strip any blanks
  441.  * from the beginning and end of the string.
  442.  */
  443.  
  444. strcpyblnks(dest,src,num)
  445. int num;
  446. char *dest, *src;
  447. {
  448.     int num_blanks = 0;
  449.  
  450.     while (*src == ' ') {
  451.         src++;
  452.         num--;
  453.     }
  454.  
  455.     for (; num>0; num--, src++) {
  456.  
  457.         if (*src == '\r' || *src == '\n') {
  458.             *dest++ = '\0';
  459.             return;
  460.         }
  461.  
  462.         if (*src == ' ')
  463.             num_blanks++;
  464.  
  465.         else {
  466.             for (; num_blanks; num_blanks--)
  467.                 *dest++ = ' ';
  468.  
  469.             *dest++ = *src;
  470.         }
  471.     }
  472.  
  473.     *dest = '\0';
  474. }
  475.